package com.lzy.token;

import com.google.gson.Gson;
import com.lzy.constant.ResultCodeEnum;
import com.lzy.global.user_info.CurrentThreadLoginUserInfo;
import com.lzy.model.RestResponseResult;
import com.lzy.util.ResultThreadLocalUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.util.AntPathMatcher;
import org.springframework.util.StringUtils;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.Set;

/**
 * com.lzy.interceptor.token 解析接口
 *
 * @author lzy
 */
@Slf4j
public abstract class TokenParser {
    private final static String TOKEN_PREFIX = "Bearer";

    /**
     * 解析token
     *
     * @param request 请求 request
     * @return
     */
    public abstract Object parserToken(HttpServletRequest request);

    /**
     * 校验权限
     *
     * @param request  请求 request
     * @param response 请求返回 response
     * @return
     * @
     */
    public abstract boolean authorization(HttpServletRequest request, HttpServletResponse response);

    /**
     * 获取请求中的token字符串
     *
     * @param request 请求request
     * @return
     */
    protected String getTokenByRequest(HttpServletRequest request) {
        String token = request.getHeader("Authorization");
        return StringUtils.isEmpty(token) ? "" : token.replace(TOKEN_PREFIX, "").trim();
    }

    /**
     * 获取用户id
     *
     * @param request
     * @return
     */
    protected Long getUserIdByRequest(HttpServletRequest request) {
        String id = request.getHeader(CurrentThreadLoginUserInfo.USER_LOGIN_THREAD_KEY_USER_ID);
        if (StringUtils.isEmpty(id)) {
            return null;
        }
        try {
            return Long.valueOf(id.trim());
        } catch (Exception e) {
            log.error("id is not Long data", e);
            return null;
        }
    }

    /**
     * 获取用户id
     *
     * @param request
     * @return
     */
    protected String getUserNameByRequest(HttpServletRequest request) {
        return request.getHeader(CurrentThreadLoginUserInfo.USER_LOGIN_THREAD_KEY_USER_NAME);
    }

    /**
     * 获取用户id
     *
     * @param request
     * @return
     */
    protected String getOpenIdByRequest(HttpServletRequest request) {
        return request.getHeader(CurrentThreadLoginUserInfo.USER_LOGIN_THREAD_KEY_OPEN_ID);
    }

    /**
     * 获取用户id
     *
     * @param request
     * @return
     */
    protected String getPhoneByRequest(HttpServletRequest request) {
        return request.getHeader(CurrentThreadLoginUserInfo.USER_LOGIN_THREAD_KEY_PHONE);
    }


    /**
     * 获取请求中的url
     *
     * @param request 请求request
     * @return
     */
    protected String getUrlByRequest(HttpServletRequest request) {
        String requestURI = request.getRequestURI();
        if (requestURI.startsWith("/")) {
            return requestURI.substring(1);
        }
        return requestURI;
    }

    /**
     * 获取请求中的 tenantId
     *
     * @param request 请求request
     * @return
     */
    protected Long getTenantIdByRequest(HttpServletRequest request) {
        String tenantId = request.getHeader("tenantId");
        if (StringUtils.isEmpty(tenantId)) {
            return null;
        }
        try {
            return Long.valueOf(tenantId.trim());
        } catch (Exception e) {
            log.error("tenantId is not Long data", e);
            return null;
        }
    }

    /**
     * 获取请求中的appId
     *
     * @param request
     * @return
     */
    protected String getAppIdByRequest(HttpServletRequest request) {
        return request.getHeader("appId");
    }


    /**
     * 返回json数据
     *
     * @param codeEnum
     * @param response
     */
    protected void returnJsonData(ResultCodeEnum codeEnum, HttpServletResponse response) {
        RestResponseResult<Object> restResponse = RestResponseResult.failResponse(codeEnum);
        String json = new Gson().toJson(restResponse);
        PrintWriter writer = null;
        response.setCharacterEncoding("UTF-8");
        response.setContentType("application/json; charset=utf-8");
        try {
            writer = response.getWriter();
            writer.print(json);
            ResultThreadLocalUtil.setRestResponse(restResponse);
        } catch (IOException e) {
            log.error("response error", e);
        } finally {
            if (writer != null) {
                writer.close();
            }
        }
    }

    /**
     * 匹配无有可用的url
     *
     * @param urls url集合
     * @param path 请求url
     * @return
     */
    protected boolean match(Set<String> urls, String path) {
        AntPathMatcher antPathMatcher = new AntPathMatcher();
        for (String url : urls) {
            if (antPathMatcher.match(url, path)) {
                return Boolean.TRUE;
            }
        }
        return Boolean.FALSE;
    }
}
